package com.openthree.common.oss;

import com.openthree.common.utils.DateUtils;
import org.apache.commons.lang.StringUtils;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.util.Calendar;
import java.util.Date;
import java.util.UUID;

/**
 * 云存储(支持七牛、阿里云、腾讯云、又拍云)
 * @author mhj
 * @email 254784163@qq.com
 * @date 2017-03-25 14:58
 */
public abstract class CloudStorageService {
    /** 云存储配置信息 */
    CloudStorageConfig config;

    /**
     * 文件路径
     * @param prefix 前缀
     * @return 返回上传路径
     */
    public String getPath(String prefix) {
        //生成uuid
        String uuid = UUID.randomUUID().toString().replaceAll("-", "");
        //文件路径
        String path = DateUtils.format(new Date(), "yyyyMMdd") + "/" + uuid;

        if(StringUtils.isNotBlank(prefix)){
            path = prefix + "/" + path;
        }

        return path;
    }

    /**
     * 上传文件-文件夹拼接(a/b/c/+filename)(流的形式-ecs免流量)
     * @param inputStream 文件流
     * @param folder 文件夹
     * @param fileName 文件名字(保留后缀)
     * @return 保存的文件key
     */
    public abstract String uploadObjectByInputStream(InputStream inputStream, String folder, String fileName);

    /**
     * 上传文件-全路径(a/b/c/filename)(流的形式-ecs免流量)
     * @param inputStream 文件流
     * @param fileFullPath 文件全路径(保留后缀)
     * @return 保存的文件key
     */
    public abstract String uploadObjectByInputStream(InputStream inputStream, String fileFullPath);

    /**
     * 通过oss->File->key值 获取对应文件的流(字节-网络传输)
     * @param fileKey
     * @return
     */
    public abstract  byte[] getFileByteByKey(String fileKey) throws Exception;

    /**
     * 通过key值 获取对应文件的流(InputStream)
     * 实际上这个方法是无效的(client.shutdwon()会将流关闭 )
     * 所以可以这里进行流的操作 (比如可以参见:getFileByteByKey())
     * 把流读取到可以被保存的数据媒介中
     * @param fileKey
     * @return
     */
    public abstract InputStream getFileInputStreamByKey(String fileKey);

    /**
     * 根据文件名获取文件访问URL(外网访问-下行收费)
     * @param ossFileKey 文件名
     * @param expires URL有效时间（小时）
     * @return
     */
    public abstract String getFileUrl(String ossFileKey, int expires);
    /**
     * 原图生成缩略图url
     * @param ossFileKey
     * @return
     */
    public abstract String getSltFileUrl(String ossFileKey,String centerName) throws IOException ;

    /**
     * (private)input转字节
     * @param input
     * @return
     * @throws Exception
     */
    public byte[] toByteArray(InputStream input) throws Exception{
        ByteArrayOutputStream output = new ByteArrayOutputStream();
        byte[] buffer = new byte[4096];
        int n = 0;
        while (-1 != (n = input.read(buffer))) {
            output.write(buffer, 0, n);
        }
        return output.toByteArray();
    }

    /**
     * (private)获得指定日期之后一段时期的日期。例如某日期之后3天的日期等。
     * @param origDate 基准日期
     * @param amount 基准日期
     * @param timeUnit 时间单位，如年、月、日等。用Calendar中的常量代表
     * @return
     */
    public  final Date dateAfter(Date origDate, int amount, int timeUnit) {
        Calendar calendar = Calendar.getInstance();
        calendar.setTime(origDate);
        calendar.add(timeUnit, amount);
        return calendar.getTime();
    }

}
